#include "chatdialog.h"
#include "ui_chatdialog.h"
#include "loadingdlg.h"
#include "chatuserwid.h"
#include "conuseritem.h"
#include "tcpmanager.h"
#include "usermanager.h"

#include <QLineEdit>
#include <QAction>
#include <QRandomGenerator>


ChatDialog::ChatDialog(QWidget *parent)
    : QDialog(parent)
    , ui(new Ui::ChatDialog)
    , m_last_widget(nullptr)
    , m_mode(ChatUIMode::ChatMode)
    , m_state(ChatUIMode::ChatMode)
    , m_b_loading(false)
    , m_cur_chat_uid(0)
{
    ui->setupUi(this);

    ui->add_btn->setState("normal", "hover", "press");
    ui->add_btn->setProperty("state","normal");

    ui->search_edit->setMaxLength(15);

    // 设置搜索框的搜索图标
    QAction* searchAct = new QAction(ui->search_edit);
    searchAct->setIcon( QIcon(":/res/search.png") );
    ui->search_edit->addAction(searchAct, QLineEdit::LeadingPosition);
    ui->search_edit->setPlaceholderText(QStringLiteral("搜索"));
    // 默认不显示搜索框
    showSearch(false);

    // 设置清除搜索框的动作
    ui->search_edit->setClearButtonEnabled(true);

    // 加载用户聊天列表 TODO
    addChatUserList();

    // 加载自己的头像
    QString head_icon = UserManager::getInstance()->getIcon();
    QPixmap pixmap(head_icon); // 加载图片
    QPixmap scaledPixmap = pixmap.scaled( ui->side_head_lb->size(), Qt::KeepAspectRatio); // 将图片缩放到label的大小
    ui->side_head_lb->setPixmap(scaledPixmap); // 将缩放后的图片设置到QLabel上
    ui->side_head_lb->setScaledContents(true); // 设置QLabel自动缩放图片内容以适应大小
    ui->side_chat_lb->setProperty("state", "normal");
    ui->side_chat_lb->setState("normal", "hover", "pressed", "selected_normal", "selected_hover", "selected_pressed");
    ui->side_contact_lb->setState("normal", "hover", "pressed", "selected_normal", "selected_hover", "selected_pressed");

    addLbGroup(ui->side_chat_lb);
    addLbGroup(ui->side_contact_lb);

    // 设置聊天label为选中状态
    ui->side_chat_lb->setSelected(true);
    // 设置选中条目
    setSelectChatItem();
    // 更新聊天界面信息
    setSelectChatPage();

    // 为searchlist设置searchedit
    ui->search_list->setSearchEdit(ui->search_edit);
    //设置中心部件为chatpage
    ui->stackedWidget->setCurrentWidget(ui->chat_page);


    // 连接加载联系人的信号槽
    connect(ui->chat_user_list, &ChatUserList::sig_loading_chat_user, this, &ChatDialog::slot_loading_chat_user);
    // 连接加载联系人的信号和槽函数
    connect(ui->con_user_list, &ContactUserList::sig_loading_contact_user, this, &ChatDialog::slot_loading_contact_user);
    // 连接在联系人页面点击好友申请条目的信号
    connect(ui->con_user_list, &ContactUserList::sig_switch_apply_friend_page, this,&ChatDialog::slot_switch_apply_friend_page);
    // 切换为聊条列表联系人的侧边栏对应的显示页面
    connect(ui->side_chat_lb, &StateWidget::clicked, this,  &ChatDialog::slot_side_chat);
    // 切换为搜索联系人的侧边栏对应的显示页面
    connect(ui->side_contact_lb, &StateWidget::clicked, this, &ChatDialog::slot_side_contact);
    // 连接输入框的改变
    connect(ui->search_edit, &QLineEdit::textChanged, this, &ChatDialog::slot_text_changed);

    // 连接申请添加好友信号
    connect(TcpManager::getInstance().get(), &TcpManager::sig_friend_apply, this, &ChatDialog::slot_apply_friend);
    // 连接认证添加好友信号
    connect(TcpManager::getInstance().get(), &TcpManager::sig_add_auth_friend, this, &ChatDialog::slot_add_auth_friend);
    // 连接自己认证回复信号
    connect(TcpManager::getInstance().get(), &TcpManager::sig_auth_rsp, this, &ChatDialog::slot_auth_rsp);

    // 连接点击联系人item发出的信号和用户信息展示槽函数
    connect(ui->con_user_list, &ContactUserList::sig_switch_friend_info_page, this, &ChatDialog::slot_friend_info_page);

    // 连接searchlist跳转聊天信号
    connect(ui->search_list, &SearchList::sig_jump_chat_item, this, &ChatDialog::slot_jump_chat_item);
    // 连接从好友信息界面跳转到聊天界面的信号
    // 连接好友信息界面发送的点击事件
    connect(ui->friend_info_page, &FriendInfoPage::sig_jump_chat_item, this, &ChatDialog::slot_jump_chat_item_from_infopage);

    // 连接对端消息通知
    connect(TcpManager::getInstance().get(), &TcpManager::sig_text_chat_msg, this, &ChatDialog::slot_text_chat_msg);

    // 连接聊天列表点击信号
    connect(ui->chat_user_list, &QListWidget::itemClicked, this, &ChatDialog::slot_item_clicked);


    connect(ui->chat_page, &ChatPage::sig_append_send_chat_msg, this, &ChatDialog::slot_append_send_chat_msg);

    // 检测鼠标点击位置，判断是否清空搜索框
    this->installEventFilter(this); // 安装事件过滤器
}

ChatDialog::~ChatDialog()
{
    delete ui;
}

// 测试加载用户列表的功能
/*
void ChatDialog::addChatUserListItem()
{
    // 创建QListWidgetItem，并设置自定义的widget
    for(int i = 0; i < 13; i++){
        int randomValue = QRandomGenerator::global()->bounded(100); // 生成0到99之间的随机整数
        int str_i = randomValue % strs.size();
        int head_i = randomValue % heads.size();
        int name_i = randomValue % names.size();

        auto *chat_user_wid = new ChatUserWid();
        chat_user_wid->setInfo(names[name_i], heads[head_i], strs[str_i]);
        QListWidgetItem *item = new QListWidgetItem;
        // qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
        item->setSizeHint(chat_user_wid->sizeHint());
        ui->chat_user_list->addItem(item);
        ui->chat_user_list->setItemWidget(item, chat_user_wid);
    }
}
*/

void ChatDialog::clearLabelState(StateWidget* lb)
{
    for (auto& ele : m_lb_list) {
        if (ele == lb) {
            continue;
        }

        ele->clearState();
    }
}

void ChatDialog::closeFindDlg()
{
    ui->search_list->closeFindDlg();
}

void ChatDialog::handleGlobalMousePress(QMouseEvent *event)
{
    // 实现点击位置的判断逻辑

    // 先判断是否处于搜索模式
    if (m_mode != ChatUIMode::SearchMode) {
        return ;
    }

    // 将鼠标点击的位置转换为搜素列表坐标系的位置
    QPoint posInSeachList = ui->search_list->mapFromGlobal(event->globalPos());
    // 判断点击的位置是否在搜素列表的范围内
    if (!ui->search_list->rect().contains(posInSeachList)) {
        // 如果不在搜素列表内，则清空输入框
        ui->search_edit->clear();
        showSearch(false);
    }
}

void ChatDialog::updateChatMsg(QVector<std::shared_ptr<TextChatData> > msgdata)
{
    for (auto& msg : msgdata) {
        if (msg->m_from_uid != m_cur_chat_uid) {
            break;
        }

        ui->chat_page->appendChatMsg(msg);
    }
}

bool ChatDialog::eventFilter(QObject *watched, QEvent *event)
{
    if (event->type() == QEvent::MouseButtonPress) {
        QMouseEvent* mouseEvent = static_cast<QMouseEvent*>(event);
        handleGlobalMousePress(mouseEvent);
    }

    return QDialog::eventFilter(watched, event);
}

// ChatDialog显示的切换
void ChatDialog::showSearch(bool b_search)
{
    if (b_search) {
        ui->chat_user_list->hide();
        ui->con_user_list->hide();
        ui->search_list->show();
        // 显示搜索界面
        m_mode = ChatUIMode::SearchMode;
    } else if (m_state == ChatUIMode::ChatMode) {
        ui->con_user_list->hide();
        ui->search_list->hide();
        // 显示聊天用户列表
        ui->chat_user_list->show();
        m_mode = ChatUIMode::ChatMode;
        ui->search_list->closeFindDlg();
        ui->search_edit->clear();
        ui->search_edit->clearFocus();
    } else if (m_state == ChatUIMode::ContactMode) {
        ui->chat_user_list->hide();
        ui->search_list->hide();
        // 显示联系人
        ui->con_user_list->show();
        m_mode = ChatUIMode::ContactMode;
        ui->search_list->closeFindDlg();
        ui->search_edit->clear();
        ui->search_edit->clearFocus();
    }
}

void ChatDialog::addLbGroup(StateWidget* lb)
{
    m_lb_list.push_back(lb);
}

// 设置当前Item为被点击选中的条目
void ChatDialog::setSelectChatItem(int uid)
{
    if (ui->chat_user_list->count() <= 0) {
        return;
    }

    if (uid == 0) {
        ui->chat_user_list->setCurrentRow(0);
        QListWidgetItem *firstItem = ui->chat_user_list->item(0);
        if (!firstItem) {
            return;
        }

        // 转为widget
        QWidget *widget = ui->chat_user_list->itemWidget(firstItem);
        if (!widget) {
            return;
        }

        auto con_item = qobject_cast<ChatUserWid*>(widget);
        if (!con_item) {
            return;
        }

        m_cur_chat_uid = con_item->getUserInfo()->m_uid;

        return;
    }

    auto find_iter = m_chat_items_added.find(uid);
    if (find_iter == m_chat_items_added.end()) {
        qDebug() << "uid " << uid << " not found, set curent row 0";
        ui->chat_user_list->setCurrentRow(0);
        return;
    }

    ui->chat_user_list->setCurrentItem(find_iter.value());

    m_cur_chat_uid = uid;
}

// 设置当前与当前用户的聊天页面
void ChatDialog::setSelectChatPage(int uid)
{
    if ( ui->chat_user_list->count() <= 0) {
        return;
    }

    // 默认
    if (uid == 0) {
        auto item = ui->chat_user_list->item(0);
        // 转为widget
        QWidget* widget = ui->chat_user_list->itemWidget(item);
        if (!widget) {
            return;
        }

        auto con_item = qobject_cast<ChatUserWid*>(widget);
        if (!con_item) {
            return;
        }

        //设置信息
        auto user_info = con_item->getUserInfo();
        ui->chat_page->setUserInfo(user_info);
        return;
    }

    // 手动指定
    auto find_iter = m_chat_items_added.find(uid);
    if (find_iter == m_chat_items_added.end()) {
        return;
    }

    //转为widget
    QWidget *widget = ui->chat_user_list->itemWidget(find_iter.value());
    if (!widget) {
        return;
    }

    //判断转化为自定义的widget
    // 对自定义widget进行操作， 将item 转化为基类ListItemBase
    ListItemBase *customItem = qobject_cast<ListItemBase*>(widget);
    if (!customItem) {
        qDebug() << "qobject_cast<ListItemBase*>(widget) is nullptr......";
        return;
    }

    auto itemType = customItem->getListItemType();
    if (itemType == CHAT_USER_ITEM) {
        auto con_item = qobject_cast<ChatUserWid*>(customItem);
        if ( !con_item) {
            return;
        }

        // 设置信息
        auto user_info = con_item->getUserInfo();
        ui->chat_page->setUserInfo(user_info);

        return;
    }
}

void ChatDialog::addChatUserList()
{
    // TODO
    // 先按照好友列表加载聊天记录，等以后客户端实现聊天记录数据库之后再按照最后信息排序
    auto friend_list = UserManager::getInstance()->getChatListPerPage();
    if (!friend_list.empty()) {
        for (auto & friend_ele : friend_list) {
            auto find_iter = m_chat_items_added.find(friend_ele->m_uid);
            if (find_iter != m_chat_items_added.end()){
                continue;
            }
            auto *chat_user_wid = new ChatUserWid();
            auto user_info = std::make_shared<UserInfo>(friend_ele);
            chat_user_wid->setInfo(user_info);
            QListWidgetItem *item = new QListWidgetItem;
            //qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
            item->setSizeHint(chat_user_wid->sizeHint());
            ui->chat_user_list->addItem(item);
            ui->chat_user_list->setItemWidget(item, chat_user_wid);
            m_chat_items_added.insert(friend_ele->m_uid, item);
        }

        // 更新已加载条目
        UserManager::getInstance()->updateChatLoadedCount();
    }

    // 模拟测试条目 TODO
    // 创建QListWidgetItem，并设置自定义的widget
    for (int i = 0; i < 13; ++ i) {
        int randomValue = QRandomGenerator::global()->bounded(100); // 生成0到99之间的随机整数
        int str_i = randomValue%strs.size();
        int head_i = randomValue%heads.size();
        int name_i = randomValue%names.size();

        auto *chat_user_wid = new ChatUserWid();
        auto user_info = std::make_shared<UserInfo>(0,names[name_i],
                                                    names[name_i],heads[head_i],0,strs[str_i]);
        chat_user_wid->setInfo(user_info);
        QListWidgetItem *item = new QListWidgetItem;
        //qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
        item->setSizeHint(chat_user_wid->sizeHint());
        ui->chat_user_list->addItem(item);
        ui->chat_user_list->setItemWidget(item, chat_user_wid);
    }
}

// 加载更多的好友条目
void ChatDialog::loadMoreChatUser()
{
    auto friend_list = UserManager::getInstance()->getChatListPerPage();
    if (!friend_list.empty()) {
        for (auto& friend_ele : friend_list) {
            auto find_iter = m_chat_items_added.find(friend_ele->m_uid);
            if (find_iter != m_chat_items_added.end()) {
                continue;
            }
            auto *chat_user_wid = new ChatUserWid();
            auto user_info = std::make_shared<UserInfo>(friend_ele);
            chat_user_wid->setInfo(user_info);
            QListWidgetItem *item = new QListWidgetItem;
            //qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
            item->setSizeHint(chat_user_wid->sizeHint());
            ui->chat_user_list->addItem(item);
            ui->chat_user_list->setItemWidget(item, chat_user_wid);
            m_chat_items_added.insert(friend_ele->m_uid, item);
        }

        //更新已加载条目
        UserManager::getInstance()->updateChatLoadedCount();
    }
}

// 加载更多的联系人
void ChatDialog::loadMoreConUser()
{
    auto friend_list = UserManager::getInstance()->getConListPerPage();
    if (!friend_list.empty()) {
        for(auto& friend_ele : friend_list) {
            auto *chat_user_wid = new ConUserItem();
            chat_user_wid->setInfo(friend_ele->m_uid,friend_ele->m_name,
                                   friend_ele->m_icon);
            QListWidgetItem *item = new QListWidgetItem;
            //qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
            item->setSizeHint(chat_user_wid->sizeHint());
            ui->con_user_list->addItem(item);
            ui->con_user_list->setItemWidget(item, chat_user_wid);
        }

        //更新已加载条目
        UserManager::getInstance()->updateContactLoadedCount();
    }
}

// 处理加载新用户的信号(到滚动条到达底部后，开始加载剩下的用户)
void ChatDialog::slot_loading_chat_user()
{
    if (m_b_loading) {
        return;
    }

    m_b_loading = true;
    LoadingDlg *loadingDialog = new LoadingDlg(this);
    loadingDialog->setModal(true);
    loadingDialog->show();
    qDebug() << "add new data to list......";
    loadMoreChatUser();
    // 加载完成后关闭对话框
    loadingDialog->deleteLater();

    m_b_loading = false;
}

// 处理加载新联系人的信号(到滚动条到达底部后，开始加载剩下的联系人)
void ChatDialog::slot_loading_contact_user()
{
    qDebug() << "slot loading contact user";
    if (m_b_loading) {
        return;
    }

    m_b_loading = true;
    LoadingDlg *loadingDialog = new LoadingDlg(this);
    loadingDialog->setModal(true);
    loadingDialog->show();
    qDebug() << "add new data to list.....";
    loadMoreConUser();
    // 加载完成后关闭对话框
    loadingDialog->deleteLater();

    m_b_loading = false;
}

void ChatDialog::slot_side_chat()
{
    qDebug() << "receive side chat clicked";
    clearLabelState(ui->side_chat_lb);
    ui->stackedWidget->setCurrentWidget(ui->chat_page);
    m_state = ChatUIMode::ChatMode;
    showSearch(false);
}

void ChatDialog::slot_side_contact()
{
    qDebug()<< "receive side contact clicked";
    clearLabelState(ui->side_contact_lb);
    //设置
    ui->stackedWidget->setCurrentWidget(ui->friend_apply_page);
    m_state = ChatUIMode::ContactMode;
    showSearch(false);
}

void ChatDialog::slot_text_changed(const QString& str)
{
    if (!str.isEmpty()) {
        showSearch(true);
    }
}

void ChatDialog:: slot_apply_friend(std::shared_ptr<AddFriendApply> apply)
{
    qDebug() << "receive apply friend slot, applyuid is " << apply->m_from_uid << " name is "
             << apply->m_name << " desc is " << apply->m_desc;

    bool b_already = UserManager::getInstance()->alreadyApply(apply->m_from_uid);
    if (b_already) {
        return;
    }

    UserManager::getInstance()->addApplyList(std::make_shared<ApplyInfo>(apply));
    ui->side_contact_lb->showRedPoint(true);
    ui->con_user_list->showRedPoint(true);
    ui->friend_apply_page->addNewApply(apply);
}

// 处理添加好友时的信息检验
void ChatDialog::slot_add_auth_friend(std::shared_ptr<AuthInfo> auth_info)
{
    qDebug() << "receive slot_add_auth__friend uid is " << auth_info->m_uid
             << " name is " << auth_info->m_name << " nick is " << auth_info->m_nick;

    // 判断如果已经是好友则跳过
    auto bfriend = UserManager::getInstance()->checkFriendById(auth_info->m_uid);
    if (bfriend) {
        return;
    }

    UserManager::getInstance()->addFriend(auth_info);

    int randomValue = QRandomGenerator::global()->bounded(100); // 生成0到99之间的随机整数
    int str_i = randomValue % strs.size();
    int head_i = randomValue % heads.size();
    int name_i = randomValue % names.size();

    auto* chat_user_wid = new ChatUserWid();
    auto user_info = std::make_shared<UserInfo>(auth_info);
    chat_user_wid->setInfo(user_info);
    QListWidgetItem* item = new QListWidgetItem;
    // qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
    item->setSizeHint(chat_user_wid->sizeHint());
    ui->chat_user_list->insertItem(0, item);
    ui->chat_user_list->setItemWidget(item, chat_user_wid);
    m_chat_items_added.insert(auth_info->m_uid, item);
}

// 处理好友检验的会包
void ChatDialog::slot_auth_rsp(std::shared_ptr<AuthRsp> auth_rsp)
{
    qDebug() << "receive slot_auth_rsp uid is " << auth_rsp->m_uid
             << " name is " << auth_rsp->m_name << " nick is " << auth_rsp->m_nick;

    //判断如果已经是好友则跳过
    auto bfriend = UserManager::getInstance()->checkFriendById(auth_rsp->m_uid);
    if (bfriend) {
        return;
    }

    UserManager::getInstance()->addFriend(auth_rsp);
    int randomValue = QRandomGenerator::global()->bounded(100); // 生成0到99之间的随机整数
    int str_i = randomValue % strs.size();
    int head_i = randomValue % heads.size();
    int name_i = randomValue % names.size();

    auto* chat_user_wid = new ChatUserWid();
    auto user_info = std::make_shared<UserInfo>(auth_rsp);
    chat_user_wid->setInfo(user_info);
    QListWidgetItem* item = new QListWidgetItem;
    //qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
    item->setSizeHint(chat_user_wid->sizeHint());
    ui->chat_user_list->insertItem(0, item);
    ui->chat_user_list->setItemWidget(item, chat_user_wid);
    m_chat_items_added.insert(auth_rsp->m_uid, item);
}

// 处理从好友申请界面跳转到聊天界面的信号
void ChatDialog::slot_jump_chat_item(std::shared_ptr<SearchInfo> search_info)
{
    qDebug() << "slot jump chat item";
    auto find_iter = m_chat_items_added.find(search_info->m_uid);
    if (find_iter != m_chat_items_added.end()) {
        qDebug() << "jump to chat item , uid is " << search_info->m_uid;
        ui->chat_user_list->scrollToItem(find_iter.value());
        ui->side_chat_lb->setSelected(true);
        setSelectChatItem(search_info->m_uid);
        // 更新聊天界面信息
        setSelectChatPage(search_info->m_uid);
        slot_side_chat();
    }

    // 如果没找到，则创建新的插入listwidget
    auto* chat_user_wid = new ChatUserWid();
    auto user_info = std::make_shared<UserInfo>(search_info);
    chat_user_wid->setInfo(user_info);
    QListWidgetItem* item = new QListWidgetItem;
    //qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
    item->setSizeHint(chat_user_wid->sizeHint());
    ui->chat_user_list->insertItem(0, item);
    ui->chat_user_list->setItemWidget(item, chat_user_wid);

    m_chat_items_added.insert(search_info->m_uid, item);

    ui->side_chat_lb->setSelected(true);
    setSelectChatItem(search_info->m_uid);
    //更新聊天界面信息
    setSelectChatPage(search_info->m_uid);
    slot_side_chat();
}

// 处理用户信息显示的跳转信号
void ChatDialog::slot_friend_info_page(std::shared_ptr<UserInfo> user_info)
{
    qDebug() << "receive switch friend info page sig";
    m_last_widget = ui->friend_info_page;
    ui->stackedWidget->setCurrentWidget(ui->friend_info_page);
    ui->friend_info_page->setInfo(user_info);
}

// 处理切换到好友申请界面的信号 进行页面跳转
void ChatDialog::slot_switch_apply_friend_page()
{
    qDebug() << "receive switch apply friend page sig";
    m_last_widget = ui->friend_apply_page;
    ui->stackedWidget->setCurrentWidget(ui->friend_apply_page);
}

// 处理从好友信息界面切换到聊天界面的信号 进行页面跳转
void ChatDialog::slot_jump_chat_item_from_infopage(std::shared_ptr<UserInfo> user_info)
{
    qDebug() << "slot jump chat item ";
    auto find_iter = m_chat_items_added.find(user_info->m_uid);
    if (find_iter != m_chat_items_added.end()) {
        qDebug() << "jump to chat item , uid is " << user_info->m_uid;
        ui->chat_user_list->scrollToItem(find_iter.value());
        ui->side_chat_lb->setSelected(true);
        setSelectChatItem(user_info->m_uid);
        //更新聊天界面信息
        setSelectChatPage(user_info->m_uid);
        slot_side_chat();
        return;
    }

    //如果没找到，则创建新的插入listwidget
    auto* chat_user_wid = new ChatUserWid();
    chat_user_wid->setInfo(user_info);
    QListWidgetItem* item = new QListWidgetItem;
    //qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
    item->setSizeHint(chat_user_wid->sizeHint());
    ui->chat_user_list->insertItem(0, item);
    ui->chat_user_list->setItemWidget(item, chat_user_wid);

    m_chat_items_added.insert(user_info->m_uid, item);

    ui->side_chat_lb->setSelected(true);
    setSelectChatItem(user_info->m_uid);
    //更新聊天界面信息
    setSelectChatPage(user_info->m_uid);
    slot_side_chat();
}

// 处理条目被点击的信号
void ChatDialog::slot_item_clicked(QListWidgetItem *item)
{
    QWidget *widget = ui->chat_user_list->itemWidget(item); // 获取自定义widget对象
    if (!widget) {
        qDebug() << "slot item clicked widget is nullptr，，，，，，";
        return;
    }

    // 对自定义widget进行操作， 将item 转化为基类ListItemBase
    ListItemBase *customItem = qobject_cast<ListItemBase*>(widget);
    if (!customItem) {
        qDebug() << "slot item clicked widget is nullptr，，，，，，";
        return;
    }

    auto itemType = customItem->getListItemType();
    if (itemType == ListItemType::INVALID_ITEM || itemType == ListItemType::GROUP_TIP_ITEM){
        qDebug() << "slot invalid item clicked，，，，，，";
        return;
    }

    if (itemType == ListItemType::CHAT_USER_ITEM) {
        // 创建对话框，提示用户
        qDebug() << "contact user item clicked，，，，，，";

        auto chat_wid = qobject_cast<ChatUserWid*>(customItem);
        auto user_info = chat_wid->getUserInfo();
        //跳转到聊天界面
        ui->chat_page->setUserInfo(user_info);
        m_cur_chat_uid = user_info->m_uid;

        return;
    }
}

// 处理缓存最新的聊天消息的信号
void ChatDialog::slot_append_send_chat_msg(std::shared_ptr<TextChatData> msgdata)
{
    if (m_cur_chat_uid == 0) {
        return;
    }

    auto find_iter = m_chat_items_added.find(m_cur_chat_uid);
    if (find_iter == m_chat_items_added.end()) {
        return;
    }

    // 转为widget
    QWidget* widget = ui->chat_user_list->itemWidget(find_iter.value());
    if (!widget) {
        return;
    }

    // 判断转化为自定义的widget
    // 对自定义widget进行操作， 将item 转化为基类ListItemBase
    ListItemBase* customItem = qobject_cast<ListItemBase*>(widget);
    if (!customItem) {
        qDebug() << "qobject_cast<ListItemBase*>(widget) is nullptr......";
        return;
    }

    auto itemType = customItem->getListItemType();
    if (itemType == CHAT_USER_ITEM) {
        auto con_item = qobject_cast<ChatUserWid*>(customItem);
        if (!con_item) {
            return;
        }

        // 设置信息
        auto user_info = con_item->getUserInfo();
        user_info->m_chat_msgs.push_back(msgdata);
        QVector<std::shared_ptr<TextChatData>> msg_vec;
        msg_vec.push_back(msgdata);
        UserManager::getInstance()->appendFriendChatMsg(m_cur_chat_uid, msg_vec);

        return;
    }
}

// 处理提示有新发送过来的消息的信号
void ChatDialog::slot_text_chat_msg(std::shared_ptr<TextChatMsg> msg)
{
    // 先查找是否存在当前用户的条目
    auto find_iter = m_chat_items_added.find(msg->m_from_uid);
    if (find_iter != m_chat_items_added.end()) {
        qDebug() << "set chat item msg, uid is " << msg->m_from_uid;
        QWidget *widget = ui->chat_user_list->itemWidget(find_iter.value());
        auto chat_wid = qobject_cast<ChatUserWid*>(widget);
        if (!chat_wid) {
            return;
        }
        // TODO
        chat_wid->updateLastMsg(msg->m_chat_msgs);
        // 更新当前聊天页面记录
        updateChatMsg(msg->m_chat_msgs);
        UserManager::getInstance()->appendFriendChatMsg(msg->m_from_uid, msg->m_chat_msgs);

        return;
    }

    // 如果没找到，则创建新的插入listwidget
    auto* chat_user_wid = new ChatUserWid();
    //查询好友信息
    auto fi_ptr = UserManager::getInstance()->getFriendById(msg->m_from_uid);
    chat_user_wid->setInfo(fi_ptr);
    QListWidgetItem* item = new QListWidgetItem;
    //qDebug()<<"chat_user_wid sizeHint is " << chat_user_wid->sizeHint();
    item->setSizeHint(chat_user_wid->sizeHint());
    chat_user_wid->updateLastMsg(msg->m_chat_msgs);
    UserManager::getInstance()->appendFriendChatMsg(msg->m_from_uid, msg->m_chat_msgs);
    ui->chat_user_list->insertItem(0, item);
    ui->chat_user_list->setItemWidget(item, chat_user_wid);
    m_chat_items_added.insert(msg->m_from_uid, item);
}
